from abc import ABC, abstractmethod

# 抽象产品
class Phone(ABC):
    @abstractmethod
    def laugh(self):
        pass

class Computer(ABC):
    @abstractmethod
    def laugh(self):
        pass

# 具体产品
class Iphone(Phone):
    def laugh(self):
        print("Iphone laughs!")

class MiPhone(Phone):
    def laugh(self):
        print("MiPhone laughs!")

class MacBook(Computer):
    def laugh(self):
        print("MacBook laughs!")

class MiBook(Computer):
    def laugh(self):
        print("MiBook laughs!")

# 抽象工厂
class AbstractFactory(ABC):
    @abstractmethod
    def phone(self) -> Phone:
        pass

    @abstractmethod
    def computer(self) -> Computer:
        pass

# 具体工厂
class AppleFactory(AbstractFactory):
    def phone(self) -> Phone:
        return Iphone()

    def computer(self) -> Computer:
        return MacBook()

class MiFactory(AbstractFactory):
    def phone(self) -> Phone:
        return MiPhone()

    def computer(self) -> Computer:
        return MiBook()

# 客户端代码
def client_code(factory: AbstractFactory):
    phone = factory.phone()
    computer = factory.computer()
    phone.laugh()
    computer.laugh()

# 测试
if __name__ == "__main__":
    print("Client: Testing Apple's factory.")
    client_code(AppleFactory())
    print("\nClient: Testing Mi's factory.")
    client_code(MiFactory())

#     代码实现:Client: Testing Apple's factory.
# Iphone laughs!
# MacBook laughs!
#
# Client: Testing Mi's factory.
# MiPhone laughs!
# MiBook laughs!